#include "cminimonthview.h"

#include <buola/image/cimage.h>
#include <buola/image/cgc.h>
#include <buola/image/cfont.h>
#include <buola/gui/cmenu.h>
#include <buola/gui/cconfig.h>
#include <buola/image/cpattern.h>
#include <buola/datetime/cdatetime.h>
#include <buola/widgets/cscrollbar.h>

namespace buola { namespace bcal {

CMiniMonthView::CMiniMonthView(CCalManager *pManager)
//    :   mManager(pManager)
{
    SetBackColor(img::CColor(1,1,1));

    SetPointer(gui::CPointer::STOCK_DEFAULT);

    mFont=img::CFont::GetStock(L"menu");
}

CMiniMonthView::~CMiniMonthView()
{
}

///////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////
////////////////////////// Interface //////////////////////////
///////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////

void CMiniMonthView::SetDate(const CDate &pDate)
{
    mDate=pDate;
    mValid=false;
    sChangeTitle(mDate.GetMonthYearText());
    Refresh();
}

void CMiniMonthView::SetToday()
{
    CDate lDate;
    lDate=CDate(CCalendarClock::now());
    SetDate(lDate);
}

void CMiniMonthView::Previous()
{
    SetDate(mDate.PreviousMonth());
}

void CMiniMonthView::Next()
{
    SetDate(mDate.NextMonth());
}

void CMiniMonthView::Shape()
{
    mMonthsRect={0,mFont->GetHeight(),Size().x,Size().y};
}

///////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////
/////////////////////// Event handlers ////////////////////////
///////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////

void CMiniMonthView::OnPreExpose()
{
    if(!mValid)
        Shape();
}
    
static const wchar_t *sWeekDays[]=
{
    L"Mon",
    L"Tue",
    L"Wed",
    L"Thu",
    L"Fri",
    L"Sat",
    L"Sun"
};

void CMiniMonthView::OnExpose(const gui::CExposeEvent &pE)
{
    img::CGC *lGC=pE.mGC;

    CDate lToday(CCalendarClock::now());

    CDate lDate(mDate.Year(),mDate.Month(),1);
    --lDate;
    lDate=lDate-(lDate.WeekDay()-1);

    lGC->SetSource(img::CColor(0.84,0.87,0.90));
    lGC->Path().Rect({0,0},{Size().x,mMonthsRect.t});
    lGC->FillPath();

    lGC->SetFont(mFont);

    for(int i=0;i<6;i++)
    {
        double lY=mMonthsRect.t+floor(i*mMonthsRect.h()/6);
        double lYNext=mMonthsRect.t+floor((i+1)*mMonthsRect.h()/6);

        for(int j=0;j<7;j++)
        {
            double lX=mMonthsRect.l+floor(j*mMonthsRect.w()/7);
            double lXNext=mMonthsRect.l+floor((j+1)*mMonthsRect.w()/7);
            
            if(lDate==lToday)
            {
                lGC->SetSource(img::CColor(0.88,0.92,1.0));
                lGC->Path().Rect(CPoint_d(lX,lY),CSize_d(lXNext-lX,lYNext-lY));
                lGC->FillPath();
            }
            else if(lDate==mDate)
            {
                lGC->SetSource(img::CColor(0.88,0.88,0.88));
                lGC->Path().Rect(CPoint_d(lX,lY),CSize_d(lXNext-lX,lYNext-lY));
                lGC->FillPath();
            }
            
            if(lDate.Month()==mDate.Month())
                lGC->SetSource(img::CColor(0.2,0.2,0.2));
            else
                lGC->SetSource(img::CColor(0.8,0.8,0.8));

            lGC->DrawText(CPoint_d(lXNext-2,lY+2),to_wstring(lDate.Day()),img::ETextPos::RIGHT);
            ++lDate;
        }
    }

    //draw lines
    lGC->SetSource(img::CColor(200,200,200));
    lGC->SetLineWidth(1.0);

    for(int i=0;i<6;i++)
    {
        double lY=mMonthsRect.t+floor(i*mMonthsRect.h()/6);

        lGC->Path().MoveTo(CPoint_d(mMonthsRect.l,lY+0.5));
        lGC->Path().LineTo(CPoint_d(mMonthsRect.r,lY+0.5));
        lGC->StrokePath();
    }
    
    lGC->Path().MoveTo(CPoint_d(mMonthsRect.l,mMonthsRect.b-0.5));
    lGC->Path().LineTo(CPoint_d(mMonthsRect.r,mMonthsRect.b-0.5));
    lGC->StrokePath();

    for(int j=0;j<7;j++)
    {
        double lX=mMonthsRect.l+floor(j*mMonthsRect.w()/7);
        lGC->Path().MoveTo(CPoint_d(lX+0.5,mMonthsRect.t));
        lGC->Path().LineTo(CPoint_d(lX+0.5,mMonthsRect.b));
        lGC->StrokePath();
    }

    lGC->Path().MoveTo(CPoint_d(mMonthsRect.r-0.5,mMonthsRect.t));
    lGC->Path().LineTo(CPoint_d(mMonthsRect.r-0.5,mMonthsRect.b));
    lGC->StrokePath();

    lGC->SetSource(img::CColor(0.2,0.2,0.2));
    lGC->SetStockFont(L"small");

    for(int j=0;j<7;j++)
    {
        double lX=mMonthsRect.l+floor((j+0.5)*mMonthsRect.w()/7);
        lGC->DrawText(CPoint_d(lX,mMonthsRect.t),sWeekDays[j],img::ETextPos::HCENTER|img::ETextPos::BOTTOM);
    }
}    

void CMiniMonthView::OnButtonDown(const gui::CMouseEvent &pE)
{
}

void CMiniMonthView::OnButtonUp(const gui::CMouseEvent &pE)
{
}

void CMiniMonthView::OnSize(const gui::CGeometryEvent &pE)
{
    mValid=false;
}

void CMiniMonthView::OnStyleChanged(TStyle)
{
//  Refresh();
}

/*namespace buola*/ } /*namespace bcal*/ }
